home *** CD-ROM | disk | FTP | other *** search
- #include "fs.h"
-
- /* a BLCK is a block number. Blocksize in bytes = SectorSize * SectorsPerBlock.
-
- BLCK pointers are used throughout the filesystem. All structures which
- require to associate themselves with another structure do so using BLCK
- pointers. Byte pointers are not used. */
-
- typedef unsigned long BLCK;
- typedef BLCK BLCKn;
-
- #define OBJECTCONTAINER_ID MAKE_ID('O','B','J','C')
- #define HASHTABLE_ID MAKE_ID('H','T','A','B')
- #define SOFTLINK_ID MAKE_ID('S','L','N','K')
-
- #define RESTOREINDEX_ID MAKE_ID('R','S','T','I')
- #define TRANSACTIONSTORAGE_ID MAKE_ID('T','R','S','T')
- #define TRANSACTIONFAILURE_ID MAKE_ID('T','R','F','A')
- #define TRANSACTIONOK_ID MAKE_ID('T','R','O','K')
-
- /* a NODE is the number of a fsNode structure in a fsNodeContainer */
-
- typedef unsigned long NODE;
-
-
-
- /* Below is the standard block header. This header is found before EVERY
- type of block used in the filesystem, except data blocks.
-
- The id field is used to check if the block is of the correct type when
- it is being referred to using a BLCK pointer.
-
- The checksum field is the SUM of all LONGs in a block plus one, and then
- negated. When applying a checksum the checksum field itself should be
- set to zero. The checking a checksum the checksum is okay if the result
- of the checksum equals zero.
-
- The ownblock BLCK pointer points to the block itself. This field is an
- extra safety check to ensure we are using a valid block. */
-
- struct fsBlockHeader {
- ULONG id; /* 4 character id string of this block */
- ULONG checksum; /* The checksum */
- BLCK ownblock; /* The blocknumber of the block this block is stored at */
- };
-
-
-
- /* Now follows the structure of the Boot block. The Boot block is always
- located at block offset 0. It contains only a version number at the
- moment to identify the block structure of the disk. */
-
- struct fsBootBlock {
- struct fsBlockHeader bheader;
-
- UWORD version; /* Version number of the filesystem block structure */
- };
-
- #define STRUCTURE_VERSION (2)
-
-
-
- /* The fsRootInfo structure has all kinds of information about the format
- of the disk. */
-
- struct fsRootInfo {
- ULONG datecreated;
-
- BLCK lastallocatedblock; /* Block which was most recently allocated */
- BLCK lastallocatedadminspace; /* AdminSpaceContainer which most recently was used to allocate a block */
- NODE lastallocatedextentnode; /* ExtentNode which was most recently created */
- NODE lastallocatedobjectnode; /* ObjectNode which was most recently created */
-
- BLCK objectnodeindex;
- BLCK rovingpointer;
- };
-
-
-
- /* An SFS disk has two Root blocks, one located at the start of
- the partition and one at the end. On startup the fs will check
- both Roots to see if it is a valid SFS disk. If either one is
- missing SFS can still continue.
-
- A Root block could be missing on purpose. For example, if you
- extend the partition at the end (adding a few MB's) then SFS
- can detect this with the information stored in the Root block
- located at the beginning (since only the end-offset has changed).
- Same goes for the other way around, as long as you don't change
- start and end point at the same time.
-
- When a Root block is missing because the partition has been
- made a bit larger, then SFS will in the future be able to
- 'resize' itself without re-formatting the disk. */
-
- struct fsRootBlock {
- struct fsBlockHeader bheader;
-
- UWORD version; /* Version number of the filesystem block structure */
- UWORD sequencenumber; /* The Root with the highest sequencenumber is valid */
-
- ULONG datecreated; /* Creation date (when first formatted). Cannot be changed. */
- UBYTE bits; /* various settings, see defines below. */
- UBYTE pad1;
- UWORD pad2;
-
- ULONG reserved1[2];
-
- ULONG firstbyteh; /* The first byte of our partition from the start of the */
- ULONG firstbyte; /* disk. firstbyteh = upper 32 bits, firstbyte = lower 32 bits. */
-
- ULONG lastbyteh; /* The last byte of our partition, excluding this one. */
- ULONG lastbyte;
-
- BLCK totalblocks; /* size of this partition in blocks */
- ULONG blocksize; /* blocksize used */
-
- ULONG reserved2[2];
- ULONG reserved3[8];
-
- BLCK bitmapbase; /* location of the bitmap */
- BLCK adminspacecontainer; /* location of first adminspace container */
- BLCK rootobjectcontainer; /* location of the root objectcontainer */
- BLCK extentbnoderoot; /* location of the root of the extentbnode B-tree */
-
- ULONG reserved4[4];
- };
-
- #define ROOTBITS_CASESENSITIVE (128) /* When set, filesystem names are treated case
- insensitive (NOT IMPLEMENTED, RESERVED FOR FUTURE USE) */
-
-
- /* Below is the structure describing an Object. Objects can be files or
- directories. Multiple Objects can be stored in an ObjectContainer
- block.
-
- owneruid & ownergid: These are not used at the moment. They have
- been reserved for future use. They must be set to zero for now.
-
- objectnode: This field contains a number uniquely identifying this
- object. This number can be used to find out the ObjectContainer
- where the Object is stored in. It is used to refer to an Object
- without having to use BLCK pointers.
-
- protection: Contains the Object's protection bits. By default this
- field is set to 0x0000000F, which means bits R, W, E and D are set
- (note that this is opposite to what is used by AmigaDOS).
-
- data (files only): Contains the BLCK number of the first data block of
- a file. To find out where the rest of the data is located this BLCK
- number can be looked up in a special B+-Tree structure (see below).
-
- size (files only): Contains the size of a file in bytes.
-
- hashtable (directories only): A BLCK pointer. It points to a
- HashTable block.
-
- firstdirblock (directories only): This BLCK pointer points to the
- first ObjectContainer block which belongs to this directory object.
- For empty directories this field is zero.
-
- datemodified: The date of the last modification of this Object. The
- date is stored in seconds from 1-1-1978 (enough for storing 136 years)
-
- bits: See the defines below. At the moment this field can be checked
- to see if the object is a file or directory. A bit is reserved for
- links, but isn't currently used (and may or may not be used depending
- on how and if links are implemented).
-
- name: Directly following the main structure is the name of the object.
- It is zero terminated.
-
- comment: Directly following the name of the object is the comment
- field. This field is zero terminated as well (even if there is no
- comment). */
-
- struct fsObject {
- UWORD owneruid;
- UWORD ownergid;
- NODE objectnode;
- ULONG protection;
-
- union {
- struct {
- BLCK data;
- ULONG size;
- } file;
-
- struct {
- BLCK hashtable; /* for directories & root */
- BLCK firstdirblock;
- } dir;
- } object;
-
- ULONG datemodified;
- UBYTE bits;
-
- UBYTE name[0];
- UBYTE comment[0];
- };
-
- #define OTYPE_HARDLINK (32)
- #define OTYPE_LINK (64)
- #define OTYPE_DIR (128)
-
- /* SFS supports Soft links. When OTYPE_LINK is set and OTYPE_HARDLINK is
- clear then the entry is a soft link. The path of the soft link isn't
- stored with the directory entry, but instead is stored as the file
- data. */
-
-
-
- /* The fsObjectContainer structure is used to hold various Objects which
- have the same parent directory. Objects always start at 2-byte
- boundaries, which means sometimes a padding byte is inserted between
- 2 fsObject structures.
-
- parent: The node-number of the parent Object. The node number can be
- used to lookup the BLCK number of the block where the parent Object is
- located.
-
- next: The next ObjectContainer belonging to this directory or zero if
- it is the last in the chain.
-
- previous: The previous ObjectContainer belonging to this directory or
- zero if it is the first ObjectContainer.
-
- object: A variable number of fsObject structures, depending on their
- sizes and on the size of the block. The next object structure can be
- found by creating a pointer pointing to the name field of the current
- object, then skip 2 strings (name & comment) and if the address is odd,
- adding 1. */
-
- struct fsObjectContainer {
- struct fsBlockHeader bheader;
-
- NODE parent;
- BLCK next;
- BLCK previous; /* 0 for the first block in the directory chain */
-
- struct fsObject object[0];
- };
-
-
-
- /* fsHashTable is the structure of a HashTable block. It functions much
- like the HashTable found in FFS, except that it is stored in a seperate
- block. This block contains a number of hash-chains (about 120 for a
- 512 byte block). Each hash-chain is a chain of Nodes. Each Node
- contains a BLCK pointer to an Object and the node number of the next
- entry in the hash-chain.
-
- parent: The node-number of the parent object.
-
- hashentry: The node-number of the first entry of a specific
- hash-chain. */
-
- struct fsHashTable {
- struct fsBlockHeader bheader;
-
- NODE parent;
-
- NODE hashentry[0];
- };
-
-
-
- struct fsSoftLink {
- struct fsBlockHeader bheader;
-
- NODE parent;
- BLCK next;
- BLCK previous;
-
- UBYTE string[0];
- };
-
-
-
- struct fsBlockRestore {
- BLCK from; /* current location of block to restore */
- BLCK to; /* original location where the block should be restored to */
- };
-
- /* Below is the structure of the special block which is used to restore
- the disk in case of a write-failure which caused the filesystem to be
- terminated during a write operation (ie, crash, powerloss, user reset).
-
- The block below is an index to other blocks which need to be restored
- to certain positions on the disk to restore the disk to its original
- state (before the fatal write operation started).
-
- How it works:
-
- The mere presence of this block on the disk indicates that a write
- operation was interrupted. If this block is present than it needs
- to be checked and any changes which need to undone recorded in this
- block need to be executed. After succesfully undoing the changes
- this block is simply wiped. Write operations which terminate normally
- will delete this block as soon as all changed have been made succesfully
- so it will never be found on the disk unless a write operation was
- interrupted. */
-
- struct fsRestoreIndex {
- struct fsBlockHeader bheader;
-
- struct fsBlockRestore blocks[0];
- };
-
-
- /* The blocks used for storing the Transaction buffer are linked in a
- singly linked list. The data they hold is a direct copy of all
- Transaction data. */
-
- struct fsTransactionStorage {
- struct fsBlockHeader bheader;
-
- BLCK next;
-
- UBYTE data[0];
- };
-
-
- struct fsTransactionFailure {
- struct fsBlockHeader bheader;
-
- BLCK firsttransaction;
- };
-
-
-
- struct fsExtentBNode {
- ULONG key; /* data! */
- ULONG next;
- ULONG prev;
- UWORD blocks; /* The size in blocks of the region this Extent controls */
- };
-